class HashTable {

  constructor () {
    this.table = new Array(137)
    for (let i = 0; i < this.table.length; i++) {
      this.table[i] = []
    }
  }

  simpleHash (data) {
    let total = 0
    for (let i = 0; i < data.length; i++) {
      total += data.charCodeAt(i)
    }
    return total % this.table.length
  }

  betterHash (string) {
    const H = 37
    var total = 0
    for (var i = 0; i < string.length; ++i) {
      total += H * total + string.charCodeAt(i)
    }
    total = total % this.table.length
    if (total < 0) {
      total += this.table.length - 1
    }
    console.log('Hash value: ' + string + ' -> ' + total)
    return parseInt(total)
  }

  put (key, value) {
    let pos = this.betterHash(key), index = 0
    while (this.table[pos][index] !== undefined) {++index}
    this.table[pos][index] = key
    this.table[pos][index + 1] = value
  }

  get (key) {
    let pos = this.betterHash(key), index = 0
    if (pos === -1) return
    while (this.table[pos][index] !== key) {index += 2}
    return this.table[pos][index + 1]
  }

  showDistro () {
    for (var i = 0; i < this.table.length; ++i) {
      if (this.table[i][0] !== undefined) {
        console.log(i + ': ' + this.table[i])
      }
    }
  }
}


var hTable = new HashTable();
var someNames = ["David", "Jennifer", "Donnie", "Raymond",
  "Cynthia", "Mike", "Clayton", "Danny", "Jonathan"];
for (var i = 0; i < someNames.length; ++i) {
  hTable.put(someNames[i]);
}
hTable.showDistro();

